package com.example.demo.rabbitmq.config;

import org.springframework.amqp.core.Binding;
import org.springframework.amqp.core.BindingBuilder;
import org.springframework.amqp.core.DirectExchange;
import org.springframework.amqp.core.Queue;
import org.springframework.amqp.rabbit.config.SimpleRabbitListenerContainerFactory;
import org.springframework.amqp.rabbit.connection.CachingConnectionFactory;
import org.springframework.amqp.rabbit.connection.ConnectionFactory;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.autoconfigure.amqp.SimpleRabbitListenerContainerFactoryConfigurer;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Primary;

import java.io.IOException;
import java.util.HashMap;

/**
 * @author LIN
 * @date 2022-12-13 09:24
 */
@Configuration
public class MultiRabbitMqConfig {

//    @Value(value = "${direct.exchange.alarm}")
    private String directExchangeAlarm;

//    @Value(value = "${queue.alarm}")
    private String queueAlarm;

//    @Value("${routing.key.alarm}")
    private String routingKeyAlarm;

//    @Value(value = "${direct.exchange.alarm.second}")
    private String directExchangeAlarmSecond;

//    @Value("${queue.alarm.second}")
    private String queueAlarmSecond;

//    @Value("${routing.key.alarm.second}")
    private String routingKeyAlarmSecond;


    @Value("${spring.rabbitmq.main.host}")
    private String mainHost;

    @Value("${spring.rabbitmq.main.port}")
    private int mainPort;

    @Value("${spring.rabbitmq.main.username}")
    private String mainUserName;

    @Value("${spring.rabbitmq.main.password}")
    private String mainPassword;

    @Value("${spring.rabbitmq.second.host}")
    private String secondHost;

    @Value("${spring.rabbitmq.second.port}")
    private int secondPort;

    @Value("${spring.rabbitmq.second.username}")
    private String secondUserName;

    @Value("${spring.rabbitmq.second.password}")
    private String secondPassword;

    @Bean(name="mainConnectionFactory")
    @Primary
    public ConnectionFactory maniConnectionFactory(){
        return connectionFactory(mainHost,mainPort,mainUserName,mainPassword);
    }

//    @Bean(name = "secondConnectionFactory")
    @ConditionalOnProperty(prefix = "spring.rabbitmq.second",value = "used",havingValue = "true")
    public ConnectionFactory secondConnectionFactory(){
        return connectionFactory(secondHost,secondPort,secondUserName,secondPassword);
    }

//    @Bean(name = "mainFactory")
    @Primary
    public SimpleRabbitListenerContainerFactory mainFactory(SimpleRabbitListenerContainerFactoryConfigurer configurer,
                                                            @Qualifier("mainConnectionFactory") ConnectionFactory connectionFactory){

        SimpleRabbitListenerContainerFactory factory = new SimpleRabbitListenerContainerFactory();
        configurer.configure(factory,connectionFactory);
        return factory;
    }

//    @Bean(name = "secondFactory")
    @Primary
    @ConditionalOnProperty(prefix = "spring.rabbitmq.second",value = "used",havingValue = "true")
    public SimpleRabbitListenerContainerFactory secondFactory(SimpleRabbitListenerContainerFactoryConfigurer configurer,
                                                            @Qualifier("secondConnectionFactory") ConnectionFactory connectionFactory){

        SimpleRabbitListenerContainerFactory factory = new SimpleRabbitListenerContainerFactory();
        configurer.configure(factory,connectionFactory);
        return factory;
    }

    /**
     *    xalarm行为分析
     */
//    @Bean
    public Queue alarmQueue() {
        return new Queue(queueAlarm);
    }

//    @Bean
    DirectExchange alarmExchange() {
        return new DirectExchange(directExchangeAlarm);
    }

//    @Bean
    Binding alarmBinding() {
        return BindingBuilder.bind(alarmQueue()).to(alarmExchange()).with(routingKeyAlarm);
    }

//    @Bean
    @ConditionalOnProperty(prefix  = "spring.rabbitmq.second", value = "used", havingValue = "true")
    public String alarmTQueueSecond(@Qualifier("secondConnectionFactory") ConnectionFactory connectionFactory) throws IOException {
        HashMap<String, Object> map = new HashMap<>(16);
        // 当队列在指定的时间没有被访问(consume, basicGet, queueDeclare…)就会被删除,Features=Exp
        map.put("x-expires", 86400000);
        // 限定队列的消息的最大值长度，超过指定长度将会把最早的几条删除掉
        map.put("x-max-length", 100000);
        // 限定队列最大占用的空间大小， 一般受限于内存、磁盘的大小, Features=Lim B， 设置为200M
        map.put("x-max-length-bytes", 209715200);

        connectionFactory.createConnection().createChannel(false).queueDeclare(queueAlarmSecond, true, false, false, map);
        connectionFactory.createConnection().createChannel(false).queueBind(queueAlarmSecond, directExchangeAlarmSecond, routingKeyAlarmSecond);
        return  "alarmTQueueSecond";
    }

    private CachingConnectionFactory connectionFactory(String host,int port,String username,String password){
        CachingConnectionFactory connectionFactory = new CachingConnectionFactory();

        connectionFactory.setHost(host);
        connectionFactory.setPort(port);
        connectionFactory.setUsername(username);
        connectionFactory.setPassword(password);
        return connectionFactory;
    }

}
